package com.hzw.common;

import java.beans.PropertyDescriptor;
import java.io.File;
import java.io.IOException;
import java.lang.reflect.Field;
import java.net.JarURLConnection;
import java.net.URL;
import java.net.URLDecoder;
import java.util.ArrayList;
import java.util.Enumeration;
import java.util.LinkedHashSet;
import java.util.List;
import java.util.Optional;
import java.util.Set;
import java.util.jar.JarEntry;
import java.util.jar.JarFile;
import javax.persistence.Column;
import org.apache.commons.beanutils.PropertyUtils;

public class ClassUtils {
    public ClassUtils() {
    }

    public static Field getField(Class clazz, String fName) {
        try {
            return clazz.getDeclaredField(fName);
        } catch (NoSuchFieldException var3) {
            return clazz.getSuperclass() != Object.class ? getField(clazz.getSuperclass(), fName) : null;
        }
    }

    public static List<Field> getAllField(Class clazz) {
        List<Field> result = new ArrayList();
        PropertyDescriptor[] ps = PropertyUtils.getPropertyDescriptors(clazz);
        Field f = null;
        PropertyDescriptor[] var4 = ps;
        int var5 = ps.length;

        for(int var6 = 0; var6 < var5; ++var6) {
            PropertyDescriptor prop = var4[var6];
            f = getField(clazz, prop.getName());
            if (f != null) {
                result.add(f);
            }
        }

        return result;
    }

    public static String getProperty(Class clazz, String column) {
        Optional<Field> optional = getAllField(clazz).stream().filter((field) -> {
            Column c = (Column)field.getAnnotation(Column.class);
            if (c == null) {
                return false;
            } else {
                return c.name().equalsIgnoreCase(column);
            }
        }).findFirst();
        return optional.isPresent() ? ((Field)optional.get()).getName() : "";
    }

    public static Set<Class<?>> getClasses(String pack) {
        Set<Class<?>> classes = new LinkedHashSet();
        boolean recursive = true;
        String packageName = pack;
        String packageDirName = pack.replace('.', '/');

        try {
            Enumeration dirs = Thread.currentThread().getContextClassLoader().getResources(packageDirName);

            while(true) {
                label67:
                while(dirs.hasMoreElements()) {
                    URL url = (URL)dirs.nextElement();
                    String protocol = url.getProtocol();
                    if ("file".equals(protocol)) {
                        String filePath = URLDecoder.decode(url.getFile(), "UTF-8");
                        findAndAddClassesInPackageByFile(packageName, filePath, recursive, classes);
                    } else if ("jar".equals(protocol)) {
                        try {
                            JarFile jar = ((JarURLConnection)url.openConnection()).getJarFile();
                            Enumeration entries = jar.entries();

                            while(true) {
                                JarEntry entry;
                                String name;
                                int idx;
                                do {
                                    do {
                                        if (!entries.hasMoreElements()) {
                                            continue label67;
                                        }

                                        entry = (JarEntry)entries.nextElement();
                                        name = entry.getName();
                                        if (name.charAt(0) == '/') {
                                            name = name.substring(1);
                                        }
                                    } while(!name.startsWith(packageDirName));

                                    idx = name.lastIndexOf(47);
                                    if (idx != -1) {
                                        packageName = name.substring(0, idx).replace('/', '.');
                                    }
                                } while(idx == -1 && !recursive);

                                if (name.endsWith(".class") && !entry.isDirectory()) {
                                    String className = name.substring(packageName.length() + 1, name.length() - 6);

                                    try {
                                        classes.add(Class.forName(packageName + '.' + className));
                                    } catch (ClassNotFoundException var15) {
                                        var15.printStackTrace();
                                    }
                                }
                            }
                        } catch (IOException var16) {
                            var16.printStackTrace();
                        }
                    }
                }

                return classes;
            }
        } catch (IOException var17) {
            var17.printStackTrace();
            return classes;
        }
    }

    public static void findAndAddClassesInPackageByFile(String packageName, String packagePath, boolean recursive, Set<Class<?>> classes) {
        File dir = new File(packagePath);
        if (dir.exists() && dir.isDirectory()) {
            File[] dirfiles = dir.listFiles((filex) -> {
                return recursive && filex.isDirectory() || filex.getName().endsWith(".class");
            });
            File[] var6 = dirfiles;
            int var7 = dirfiles.length;

            for(int var8 = 0; var8 < var7; ++var8) {
                File file = var6[var8];
                if (file.isDirectory()) {
                    findAndAddClassesInPackageByFile(packageName + "." + file.getName(), file.getAbsolutePath(), recursive, classes);
                } else {
                    String className = file.getName().substring(0, file.getName().length() - 6);

                    try {
                        classes.add(Thread.currentThread().getContextClassLoader().loadClass(packageName + '.' + className));
                    } catch (ClassNotFoundException var12) {
                        var12.printStackTrace();
                    }
                }
            }

        }
    }
}

